package com.auxgroup.hr.front.service.personnal.impl;

import java.math.BigDecimal;
import java.util.*;
import java.util.stream.Collectors;

import javax.annotation.Resource;

import com.auxgroup.hr.front.commons.Constant;
import com.auxgroup.hr.front.commons.utils.DateUtils;
import com.auxgroup.hr.front.dao.domain.*;
import com.auxgroup.hr.front.dao.repository.*;
import com.auxgroup.hr.front.service.comm.SysDictService;
import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.domain.Example;
import org.springframework.data.domain.Sort;
import org.springframework.stereotype.Service;

import com.auxgroup.hr.front.commons.utils.WebServiceClient;
import com.auxgroup.hr.front.commons.utils.WebServiceUtils;
import com.auxgroup.hr.front.dozer.IObjectMapper;
import com.auxgroup.hr.front.service.personnal.PersonalDataService;
import com.auxgroup.hr.front.ws.SoapXmlBuild;

/**
 * @author wangchangyun
 * @version 创建时间：180523 个人信息表service
 */
@Service("personalDataService")
public class PersonalDataServiceImpl implements PersonalDataService {
    private static final Logger logger = LoggerFactory.getLogger(PersonalDataServiceImpl.class);

    @Autowired
    private PsCPersonalDataRepository psCPersonalDataRepository;

    @Autowired
    private PsCPayslipHdrRepository psCPayslipHdrRepository;

    @Autowired
    private PsCPayslipVw1Repository psCPayslipVw1Repository;

    @Autowired
    private PsCPayslipVw2Repository psCPayslipVw2Repository;

    @Autowired
    private PsCPyCompVwRepository psCPyCompVwRepository;

    @Autowired
    private SysDictService sysDictService;

    @Value("${ws.processService.verifypwd.soapAction}")
    private String processVerifyPwdsoapAction;

    @Autowired
    private PsCPyModVwRepository psCPyModVwRepository;

    @Autowired
    private PsoprdefnRepository psoprdefnRepository;

    @Autowired
    private PsFpSalaryExpTRepository psFpSalaryExpTRepository;

    @Value("${ws.processService.approve.address}")
    private String processURL;

    @Value("${ws.processService.getLeavebal.soapAction}")
    private String getLeavebalsoapAction;

    @Value("${ws.processService.leavetime.soapAction}")
    private String processLeaveTimesoapAction;

    @Resource(name = "dozerMapper")
    protected IObjectMapper objectMapper;

    @Override
    public PsCPersonalData getPersonalData(String emplid) {
        return psCPersonalDataRepository.findOne(emplid);
    }

    @Override
    public PsCPersonalData save(PsCPersonalData PersonalData) {
        return psCPersonalDataRepository.save(PersonalData);
    }

    @Override
    public Boolean delete(String emplId) {
        try {
            psCPersonalDataRepository.delete(emplId);
        } catch (Exception e) {
            logger.error("delete PersonalData error: personalInfo={}", emplId, e);
            return false;
        }
        return true;
    }

    @Override
    public List<PsCPersonalData> getAll() {
        PsCPersonalData PersonalData = new PsCPersonalData();
        return psCPersonalDataRepository.findAll(Example.of(PersonalData));
    }

    @Override
    public Psoprdefn getOprdefn(String oprid) {
        return psoprdefnRepository.findOne(oprid);
    }

    @Override
    public boolean loginPayroll(String emplid, String pwd) {
        StringBuilder soapXml = new StringBuilder();
        SoapXmlBuild.buildPayrollLoginSoapXml(soapXml, emplid, pwd);
        String respXml = WebServiceClient.doPostSoap(processURL, soapXml.toString(), processVerifyPwdsoapAction);
        if (StringUtils.isNotBlank(respXml)) {
            Map<String, String> transNumMap = WebServiceUtils.handleRespXml(respXml, "C_PASSWORD_VERIFY_RES");
            if (transNumMap != null && !transNumMap.isEmpty()) {
                return "0".equalsIgnoreCase(transNumMap.get("C_MSG_CODE"));
            }
        }
        return false;
    }

    @Override
    public PsCPyCompVw getPyComp(String emplid) {
        List<Object[]> objs = sysDictService.getObjectListFromSql(Constant.BASE_PAYROLL_INFO, new String[]{emplid});
        PsCPyCompVw vw = new PsCPyCompVw();
        if (!objs.isEmpty()) {
            Object[] arr = objs.get(0);
            vw.setDescr1(arr[0] == null ? "" : String.valueOf(arr[0]));
            vw.setDescr2(arr[1] == null ? "" : String.valueOf(arr[1]));
            vw.setDescr3(arr[2] == null ? "" : String.valueOf(arr[2]));
            vw.setDescr4(arr[4] == null ? (arr[5] == null ? "" : String.valueOf(arr[5])) : String.valueOf(arr[4]));
            vw.setDescr5(arr[6] == null ? "" : String.valueOf(arr[6]));
            List<String> sbs = sysDictService.getStringFromSql(Constant.SHEBAO_CENTER, new String[]{emplid});
            if (!sbs.isEmpty()) {
                vw.setDescr6(sbs.get(0));
            }
            List<String> gjcs = sysDictService.getStringFromSql(Constant.GONGJIJIN_CENTER, new String[]{emplid});
            if (!gjcs.isEmpty()) {
                vw.setDescr7(gjcs.get(0));
            }
            vw.setcComprate1(arr[8] == null ? BigDecimal.ZERO : new BigDecimal(String.valueOf(arr[8])));
            vw.setcComprate2(arr[9] == null ? BigDecimal.ZERO : new BigDecimal(String.valueOf(arr[9])));
            vw.setcComprate3(arr[10] == null ? BigDecimal.ZERO : new BigDecimal(String.valueOf(arr[10])));
            vw.setcComprate4(arr[11] == null ? BigDecimal.ZERO : new BigDecimal(String.valueOf(arr[11])));
            vw.setcComprate5(arr[12] == null ? BigDecimal.ZERO : new BigDecimal(String.valueOf(arr[12])));
        }
        return vw;

//		return psCPyCompVwRepository.findOne(emplid);
    }

    @Override
    public List<PsCPyModVw> getPyMods(String emplid) {
        PsCPyModVw queryMod = new PsCPyModVw();
        queryMod.setEmplid(emplid);
        return psCPyModVwRepository.findAll(Example.of(queryMod));
    }


    @Override
    public Map<String, String> getLeavebalInfo(String emplid) {
        StringBuilder soapXml = new StringBuilder();
        SoapXmlBuild.buildGetLeavebalSoapXml(soapXml, emplid);
        String responXml = WebServiceClient.doPostSoap(processURL, soapXml.toString(), getLeavebalsoapAction);
        return WebServiceUtils.handleRespXml(responXml, "C_GET_LEAVEBAL_RESP");
    }


    @Override
    public boolean hasPaySlipPermission(String oprid) {
        List<String> xs = sysDictService.getStringFromSql(Constant.PERMISSION_PAYSLIP, new String[]{oprid});
        return !xs.isEmpty();
    }

    @Override
    public List<PsCPayslipHdr> getPaySlip(String emplid, String year, String calrunid) {
        int yearInt = Integer.parseInt(year);
        String startDay = yearInt + "-01-01 00:00:00";
        String endDay = yearInt + "-12-31 23:59:59";
        List<Object[]> objs = sysDictService.getObjectListFromSql(Constant.PAY_SLIP_QUERY, new String[]{emplid, startDay, endDay});
        return objs.stream().map(obj -> {
            PsCPayslipHdr r = new PsCPayslipHdr();
            r.setCalRunId(String.valueOf(obj[1]));
            r.setCalPrdId(String.valueOf(obj[0]));
            r.setRunType(String.valueOf(obj[7]));
            r.setEmplid(emplid);
            r.setYear(year);
//			List<String> payrollNames = sysDictService.getStringFromSql(Constant.PAYROLL_NAME, new String[]{String.valueOf(obj[1])});
//			if(!payrollNames.isEmpty()) {
            r.setDescr(String.valueOf(obj[6]));
//			}
//
            r.setcAmt001(new BigDecimal(String.valueOf(obj[2])));
            r.setcAmt002(new BigDecimal(String.valueOf(obj[5])));
            return r;
        }).collect(Collectors.toList());

//
//		PsCPayslipHdr paySlip = new PsCPayslipHdr();
//		paySlip.setYear(year);
//		paySlip.setEmplid(emplid);
//		if(StringUtils.isNotBlank(calrunid)){
//			paySlip.setCalRunId(calrunid);
//		}
//		return psCPayslipHdrRepository.findAll(Example.of(paySlip),new Sort(Sort.Direction.DESC,"calRunId"));
    }


    @Override
    public List<Map<String, Object>> buildSlips(PsCPayslipHdr paySlip) {
        List<Map<String, Object>> slips = new ArrayList<>();
        List<Map<String, Object>> vw2Datas;
        Map<String, Object> vw1Data;
        Map<String, Object> vw2Data;


        //获取薪资组
        List<String> payrollNames = sysDictService.getStringFromSql(Constant.GP_PAYGROUP, new String[]{paySlip.getEmplid(), paySlip.getCalRunId()});
        String payGroup = payrollNames.isEmpty() ? "SHARE" : payrollNames.get(0);

        List<Object[]> lv1s = sysDictService.getObjectListFromSql(Constant.PAYROLL_DETAIL_LV1,
                new String[]{payGroup, paySlip.getEmplid(), paySlip.getCalRunId(), paySlip.getYear(), paySlip.getDescr()});
        List<Object[]> lv2s = sysDictService.getObjectListFromSql(Constant.PAYROLL_DETAIL_LV2,
                new String[]{paySlip.getEmplid(), paySlip.getCalRunId(), paySlip.getYear(), paySlip.getDescr(), payGroup});
        lv1s.sort(Comparator.comparing(x -> (BigDecimal) x[4]));
        lv2s.sort(Comparator.comparing(x -> (BigDecimal) x[6]));
        lv1s.forEach(lv1 -> {
            if (BigDecimal.ZERO.compareTo(new BigDecimal(String.valueOf(lv1[6]))) < 0) {
                Map<String, Object> vw1 = new HashMap<>();
                vw1.put("name", lv1[5]);
                vw1.put("value", lv1[6]);
                List<Map<String, Object>> children = new ArrayList<>();
                lv2s.forEach(lv2 -> {
                    if (lv1[4].equals(lv2[4]) && BigDecimal.ZERO.compareTo(new BigDecimal(String.valueOf(lv2[8]))) < 0) {
                        Map<String, Object> vw2 = new HashMap<>();
                        vw2.put("name", lv2[7]);
                        vw2.put("value", lv2[8]);
                        children.add(vw2);
                    }
                });
                vw1.put("children", children);
                slips.add(vw1);
            }
        });

        Map<String, Object> vw1 = new HashMap<>();
        String salaryDescr = getSalaryDescr(paySlip.getCalPrdId(), paySlip.getEmplid(), paySlip.getRunType());
        if (salaryDescr != null) {
            vw1.put("name", "薪资说明");
            vw1.put("value", salaryDescr);
            slips.add(vw1);
        }


//
//		//工资大类集合
//		PsCPayslipVw1 queryvw1 = objectMapper.map(paySlip, PsCPayslipVw1.class);
//		List<PsCPayslipVw1> vw1s = psCPayslipVw1Repository.findAll(Example.of(queryvw1));
//
//		//工资小类集合
//		PsCPayslipVw2 queryvw2 = objectMapper.map(paySlip, PsCPayslipVw2.class);
//		List<PsCPayslipVw2> vw2s = psCPayslipVw2Repository.findAll(Example.of(queryvw2));
//		if(vw1s!=null&&!vw1s.isEmpty()){
//			for (PsCPayslipVw1 vw1 : vw1s) {
//				if(vw1.getAmt()!=null&&vw1.getAmt().doubleValue()>0){
//					vw2Datas = new ArrayList<Map<String,Object>>();
//					vw1Data = new HashMap<String, Object>();
//					vw1Data.put("name", vw1.getName1());
//					vw1Data.put("value", vw1.getAmt());
//					for (PsCPayslipVw2 vw2 : vw2s) {
//						if(vw1.getSeqnbr().equals(vw2.getSeqnbr())){
//							if(vw2.getAmt()!=null&&vw2.getAmt().doubleValue()>0){
//								vw2Data = new HashMap<String, Object>();
//								vw2Data.put("name", vw2.getName2());
//								vw2Data.put("value", vw2.getAmt());
//								vw2Datas.add(vw2Data);
//							}
//						}
//					}
//					vw1Data.put("children", vw2Datas);
//					slips.add(vw1Data);
//				}
//			}
//		}
        return slips;
    }

    @Override
    public String getSalaryDescr(String calPrdId, String emplid, String runType) {

        PsFpSalaryExpT psFpSalaryExpT = psFpSalaryExpTRepository.findByCalPrdIdAndEmplidAndRunType(calPrdId, emplid, runType);
        if (psFpSalaryExpT != null) {
            return psFpSalaryExpT.getFpSalaryDescr();
        }
        return null;
    }

}
